package pub.guoxin.oops.auth.controller;

import com.google.common.base.Strings;
import io.swagger.annotations.ApiOperation;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.http.MediaType;
import org.springframework.security.authentication.BadCredentialsException;
import org.springframework.web.bind.annotation.*;
import pub.guoxin.oops.auth.service.AuthenticationService;
import pub.guoxin.oops.auth.service.UserService;
import pub.guoxin.oops.auth.vo.*;
import pub.guoxin.oops.common.cache.CacheService;
import pub.guoxin.oops.constants.OopsPathConstants;
import pub.guoxin.oops.enums.Authority;
import pub.guoxin.oops.model.User;
import pub.guoxin.oops.vo.ResultVo;
import pub.guoxin.oops.vo.ResultVoBuilder;

import javax.validation.Valid;
import java.util.Objects;

import static pub.guoxin.oops.common.cache.CacheKeyFormatEnums.SMS_CAPTCHA;

@RestController
@RequestMapping(OopsPathConstants.AUTH_PATH)
public class AuthenticationController {

    @Autowired
    private CacheService cacheService;
    @Autowired
    private AuthenticationService authenticationService;
    @Autowired
    private UserService userService;
    @Autowired
    private ResultVoBuilder builder;

    /**
     * @ApiImplicitParam： 用在@ApiImplicitParams注解中，指定一个请求参数的各个方面
     * paramType：参数放在哪个地方
     * header-->请求参数的获取：@RequestHeader
     * query-->请求参数的获取：@RequestParam
     * path（用于restful接口）-->请求参数的获取：@PathVariable
     * body（不常用）
     * form（不常用）
     * name：参数名
     * dataType：参数类型
     * required：参数是否必须传
     * value：参数的意思
     * defaultValue：参数的默认值
     */
    @ApiOperation(value = "登录验证", notes = "登录验证，并返回密钥")
    @PostMapping(value = "/", produces = MediaType.APPLICATION_JSON_UTF8_VALUE)
    public ResultVo<LoginUserToken> createAuthenticationToken(@Valid @RequestBody AuthVo authVo/*, Device device*/) {
        String token = null;
        try {
            token = authenticationService.createAuthenticationToken(authVo.getUsername(), authVo.getPassword());
        } catch (BadCredentialsException e) {
            return builder.buildBadRequestResultInfo("用户名或密码错误");
        }
        User user = userService.one(authVo.getUsername());
        return builder.buildSuccessResultInfo(new LoginUserToken(user, token));
    }

    @ApiOperation(value = "刷新密钥", notes = "刷新密钥")
    @GetMapping(value = "/refresh", produces = MediaType.APPLICATION_JSON_UTF8_VALUE)
    public ResultVo<AuthTokenVo> refreshAndGetAuthenticationToken(@RequestHeader String token) {
        if (Strings.isNullOrEmpty(token)) {
            return builder.buildBadRequestResultInfo();
        }
        String tokenResult = authenticationService.refreshAndGetAuthenticationToken(token);
        return builder.buildSuccessResultInfo(new AuthTokenVo(tokenResult));
    }

    @ApiOperation(value = "用户注册", notes = "用户注册")
    @PostMapping(value = "/reg", produces = MediaType.APPLICATION_JSON_UTF8_VALUE)
    public ResultVo registerUser(@Valid @RequestBody AuthRegisterVo authenticationRequest) {

        String mobile = authenticationRequest.getMobile();
        // 拿出缓存的验证码

        String cacheCaptcha = cacheService.get(SMS_CAPTCHA.key(mobile), String.class);
        if (Authority.ROLE_ROOT.equals(authenticationRequest.getAuthority())) {
            return builder.buildBadRequestResultInfo();
        }
        String captcha = authenticationRequest.getCaptcha();
        // 测试开关
        if (!captcha.equals(cacheCaptcha) && !captcha.equals("654321") && !captcha.equals("string"))
            return builder.buildBadRequestResultInfo("验证码错误");

        User user = authenticationService.addUser(authenticationRequest);
        if (Objects.isNull(user)) {
            return builder.buildBadRequestResultInfo("该手机已经被注册");
        }
        return builder.buildSuccessResultInfo();
    }

    @ApiOperation(value = "找回密码/修改密码", notes = "找回密码/修改密码")
    @PostMapping(value = "/password/reset", produces = MediaType.APPLICATION_JSON_UTF8_VALUE)
    public ResultVo modifyPassword(@Valid @RequestBody ModifyPasswordVo modifyPasswordVo) {
        // 拿出缓存的验证码
        String cacheCaptcha = cacheService.get(SMS_CAPTCHA.key(modifyPasswordVo.getUsername()), String.class);
        String captcha = modifyPasswordVo.getCaptcha();
        // 测试开关
        if (!captcha.equals(cacheCaptcha) && !captcha.equals("654321") && !captcha.equals("string"))
            return builder.buildBadRequestResultInfo("验证码错误");

        return authenticationService.modifyPassword(modifyPasswordVo.getUsername(), modifyPasswordVo.getPassword());
    }

}
